/*
 * udt_send.c
 *
 *  Created on: 2013. 10. 16.
 *      Author: jphong
 */

#include "np.h"
#include "packet.h"

static float pktErrorRate = 0.1;
static float pktLossRate = 0.1;

// Random number generations [0, 1]
static float
prob() {
	struct timeval tv;
	static unsigned int seed;

	if ( !seed ) {
		gettimeofday(&tv, NULL);
		seed = tv.tv_sec * 1000 + tv.tv_usec/1000;  // in msec unit
		srandom(seed);
	}
	return ( (float) random() / RAND_MAX );
}

// Unreliable data transfer
int
udt_send(int sockfd, const Packet *pkt, const struct sockaddr *peer, socklen_t peerlen )
{
	unsigned int pktLength;

	if ( prob() <= pktLossRate )   {
		print_pkt("Packet lost>>", pkt);
		return (0);		// Do not send the packet to simulate packet loss
	}
	pktLength = ntohs(pkt->header.len);
	if ( prob() <= pktErrorRate ) {
		int l;
		unsigned char tmp[4096];
		memcpy(tmp, (char *) pkt, pktLength);
		l =  (int) (prob() * pktLength);	
		if ( l >= pktLength )
			l = pktLength - 1;
		*(tmp+l) += 1;        // Cause bit error in l-th byte of the packet
		print_pkt("Packet Corurpted >>", (Packet *) tmp);
		return(sendto(sockfd, tmp, pktLength, 0, peer, peerlen));
	}
	print_pkt(">>", pkt);
	return(sendto(sockfd, pkt, pktLength, 0, peer, peerlen));
}
